package com.zhuiyun.project.security.customizelogin.wx;

import com.zhuiyun.project.api.wxlogin.entiy.WxUser;
import com.zhuiyun.project.api.wxlogin.mapper.WxLoginMapper;
import com.zhuiyun.project.api.wxlogin.service.impl.WxLoginServiceImpl;
import com.zhuiyun.project.api.appuser.entity.User;
import com.zhuiyun.project.api.sysuser.service.SysUserService;
import com.zhuiyun.project.common.errorCode.EmErrorCode;
import com.zhuiyun.project.security.customizelogin.usernamepasswordcode.UsernamePasswordCodeAuthenticationToken;
import com.zhuiyun.project.util.ObjectUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.AuthenticationServiceException;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.List;

/**
 * @ClassName WechatAuthenticationProvider
 * @Description 微信身份认证处理
 * @Author zcy
 * @Date 2023/4/5 15:20
 **/
@Component
public class WechatAuthenticationProvider implements AuthenticationProvider {
    @Autowired
    private WxLoginServiceImpl wxLoginService;
    @Autowired
    private WxLoginMapper wxLoginMapper;

    /**
     * * 认证处理，返回一个Authentication的实现类则代表认证成功，返回null则代表认证失败
     *
     * @param authentication
     * @return
     * @throws AuthenticationException
     */
    @Override
    public Authentication authenticate(Authentication authentication) throws AuthenticationException {
        if (!supports(authentication.getClass())) {
            return null;
        }
        WechatAuthenticationToken token = null;
        if (authentication instanceof WechatAuthenticationToken) {
            token = (WechatAuthenticationToken) authentication;
        }
        WxUser wxUser = wxLoginService.queryWxUserByOpenId(token.getOpenId());
        //获取手机号
        String userPhone = token.getUserPhone();
        //获取用户信息
        User userByPhone = wxLoginService.getUserByPhone(userPhone);
        //判断该用户的id是否在openid的userID列表中
        //未注册过，首次登录
        if (!ObjectUtils.isNotEmpty(userByPhone)) {
            userByPhone = new User();
            userByPhone.setUserPhone(userPhone);
            //首次登录
            userByPhone = wxLoginService.addUserFirst(userByPhone);
            //判断是否添加成功
            if (userByPhone == null) {
                throw new BadCredentialsException("登录失败，请重新登陆");
            }
        }
        int userId = userByPhone.getId();
        //判断openId是否存在
        if (ObjectUtils.isNotEmpty(wxUser)) {

            wxUser.setLastUserId(userId);
            //判断该user是否曾经在该微信号上登录过
            String userIds = wxUser.getUserId();
            //分割
            String[] userIdArr = userIds.split(",");
            //遍历
            long count = Arrays.stream(userIdArr).filter(s -> s.equals(String.valueOf(userId))).count();
            //存在
            if (count < 1) {
                userIds = userIds + "," + userId;
                wxUser.setUserId(userIds);
            }
            //修改
            if (wxLoginMapper.updateByPrimaryKeySelective(wxUser) < 0) {
                throw new BadCredentialsException("登录失败，请重新登陆");
            }
            //存在
        } else {
            //注册
            wxUser = new WxUser();
            wxUser.setOpenId(token.getOpenId());
            wxUser.setLastUserId(userId);
            wxUser.setDelFlag(0);
            wxUser.setCreateTime(new Date());
            wxUser.setUpdateTime(new Date());
            wxUser.setUserId(String.valueOf(userId));
            //创建
            if (wxLoginMapper.insert(wxUser) < 0) {
                throw new BadCredentialsException("登录失败，请重新登陆");
            }
        }
        //获取该账号的权限
        //获取用户信息
        List<String> list = findPermissionByAdminUserName(userByPhone.getUserType());
        List<GrantedAuthority> authorities = new ArrayList<>();
        for (String permissionCode : list) {
            if (permissionCode != null && permissionCode != "") {
                GrantedAuthority grantedAuthority =
                        new SimpleGrantedAuthority(permissionCode);
                authorities.add(grantedAuthority);
            }}
        //获取用户权限信息
        WechatAuthenticationToken result = new WechatAuthenticationToken(token.getOpenId(), userPhone, authorities);
        result.setDetails(authentication.getDetails());
        return result;
    }


    /**
     * 如果该AuthenticationProvider支持传入的Authentication对象，则返回true
     */
    @Override
    public boolean supports(Class<?> aClass) {
        return WechatAuthenticationToken.class.isAssignableFrom(aClass);
    }

    /**
    * @Author kdj
    * @Description 获取用户权限
    * @Date  10:00
    * @Return java.util.List<java.lang.String>
    * @param type
    */
    public static List<String>  findPermissionByAdminUserName(int type){
        List<String> list = new ArrayList<String>();
        //app用户权限
        list.add("app");
        //用户类型
        if(type==0){
            list.add("patient");
        }else{
            list.add("physician");
        }
        return list;
    }
}
